<?php
namespace app\common\logic;

use think\facade\Db;
/**
 * 短信类
 */
class SmsLogic 
{
    private $config;
    
    public function __construct() 
    {
        $config = Db::name('sms_set')->where('status',1)->find();
        $this->config = $config;
    }

    /**
     * 是否开启某项
     */
    public function getTpl($type){
        $sms_plate = tpCache('sms_open');
        $tpl = Db::name('sms_template')->where(['type'=>$type])->find();

        return $tpl;
    }

    /**
     * 发送短信逻辑
     * $sender 手机号
     */
    public function sendSms($type, $mobile,$username='')
    {
        if(!$type || !$mobile){
            return ['status'=>0,'msg'=>'参数有误'];
        }
        if(!$this->config['status']){
            return ['status'=>0,'msg'=>'短信功能未开启'];
        }
        //查看模板状态
        if($type){
            $smsTemp = $this->getTpl($type);
            if(!$smsTemp['status']){
                return ['status'=>0,'msg'=>'短信功能未开启'];
            }
        }


        //判断手机号
        if(!check_mobile($mobile)){
            return ['status'=>0,'msg'=>'请输入正确的手机号'];
        }
        //判断间隔
        $data = M('send_sms')->where(array('mobile'=>$mobile,'status'=>1))->order('id DESC')->find();

        //同一个ip只能发10次
        $ip = request()->ip();
        //60秒以内不可重复发送
        if($data && (time() - $data['addtime']) < 60){
            return array('status'=>0,'msg'=>'60秒内不允许重复发送');
        }
        $data = Db::name('send_sms')->where(array('ip'=>$ip,'addtime'=>['gt',getLingdian()]))->count();
        if($data>=100){
            return ['status'=>0,'msg'=>'今日发送验证码次数已达上限'];
        }
        //手机号一天只能5次
        $data = Db::name('send_sms')->where(array('mobile'=>$mobile,'addtime'=>['gt',getLingdian()]))->count();
        if($data>=100){
            return ['status'=>0,'msg'=>'今日发送验证码次数已达上限'];
        }

        //判断手机号存在
        $have = Db::name('users')->where(['mobile'=>$mobile])->field('user_id')->find();
        if($type=='reg'){//注册

        }else{
            if(!$have){
                return ['status'=>0,'msg'=>'手机号不存在'];
            }
        }
        //组装数据
        $code = intval(rand(100000, 999999));

        $param['code'] =$code;
        $shopname = tpCache('store_name');
        $param['product'] = $shopname;
        $content = $smsTemp['content'];
        //替换内容
        foreach ($param as $key => $val) {
            $content = str_replace('${' . $key . '}', $val, $content);
        }

        $smsParams = [ // 短信模板中字段的值
            18 => ['code'=>$code,'product'=>$shopname],
            20 => ['code'=>$code,'product'=>$shopname],
            21 => ['code'=>$code,'product'=>$shopname],
            22 => ['product'=>$shopname]
        ];

        //短信平台
        $type = (int)$this->config['smstype'] ?: 0;
        switch($type) {
            case 'juchen':
                $result = $this->sendSmsByJuchen($mobile, $content);
                break;
            case 'ali':
                $result = $this->sendSmsByAlidayu($mobile, $smsTemp['sname'], $smsParams[$type], $smsTemp['idsms']);
                break;
            case 'tengxun':
                $result = $this->sendSmsByTengxun($mobile, $smsTemp['sname'], $smsParams[$type], $smsTemp['idsms']);
                break;
            default:
                $result = ['status' => 0, 'msg' => '不支持的短信平台'];
        }
        if(!$result['status']){
            return $result;
        }
        //插入发送明细
        $data = array();
        if ($result['status'] == 1) {
            session('smscode',md5($code));
            $data['status'] = 0;
        }
        $dataAll = array();
        $modtime = time();
        $data['codes'] = $code;
        $data['content'] = $content;
        $data['addtime'] = $modtime;
        $data['uptime'] = $modtime + 120;
        $data['ip'] = $ip;
        $data['username'] = $username?:'';
        $m_ary = explode(',', $mobile);
        foreach ($m_ary as $m) {
            $data['mobile'] = $m;
            $dataAll[] = $data;
        }
        Db::name("send_sms")->insertAll($dataAll);

        return $result;
    }
    
   /**
    * 发送短信0
    */
    private function sendSmsByJuchen($mobile, $content){
        $send = new \app\common\util\sms\Juchen();
        $return = $send->sendMessage($this->config['accesskey'], $this->config['accesssecret'], $mobile, $content);
        if($return!=100){
            return ['status'=>0,'msg'=>$return];
        }else{
            return ['status'=>1,'msg'=>'发送成功，请注意查收'];
        }
    }

    /**
     * 发送短信（阿里大于）
     * @param $mobile  手机号码
     * @param $code    验证码
     * @return bool    短信发送成功返回true失败返回false
     */
    private function sendSmsByAlidayu($mobile, $smsSign, $smsParam, $templateCode)
    {
        //时区设置：亚洲/上海
        date_default_timezone_set('Asia/Shanghai');
        //这个是你下面实例化的类
        vendor('Alidayu.TopClient');
        //这个是topClient 里面需要实例化一个类所以我们也要加载 不然会报错
        vendor('Alidayu.ResultSet');
        //这个是成功后返回的信息文件
        vendor('Alidayu.RequestCheckUtil');
        //这个是错误信息返回的一个php文件
        vendor('Alidayu.TopLogger');
        //这个也是你下面示例的类
        vendor('Alidayu.AlibabaAliqinFcSmsNumSendRequest');

        $c = new \TopClient;
        //App Key的值 这个在开发者控制台的应用管理点击你添加过的应用就有了
        $c->appkey = $this->config['sms_appkey'];
        //App Secret的值也是在哪里一起的 你点击查看就有了
        $c->secretKey = $this->config['sms_secretKey'];
        //这个是用户名记录那个用户操作
        $req = new \AlibabaAliqinFcSmsNumSendRequest;
        //代理人编号 可选
        $req->setExtend("123456");
        //短信类型 此处默认 不用修改
        $req->setSmsType("normal");
        //短信签名 必须
        $req->setSmsFreeSignName($smsSign);
        //短信模板 必须
        $smsParam = json_encode($smsParam, JSON_UNESCAPED_UNICODE);// 短信模板中字段的值
        $req->setSmsParam($smsParam);
        //短信接收号码 支持单个或多个手机号码，传入号码为11位手机号码，不能加0或+86。群发短信需传入多个号码，以英文逗号分隔，
        $req->setRecNum("$mobile");
        //短信模板ID，传入的模板必须是在短信平台“管理中心-短信模板管理”中的可用模板。
        $req->setSmsTemplateCode($templateCode); // templateCode

        $c->format = 'json';
        //发送短信
        $resp = $c->execute($req);

        //短信发送成功返回True，失败返回false
        if ($resp && $resp->result) {
            return array('status' => 1, 'msg' => $resp->sub_msg);
        } else {
            return array('status' => -1, 'msg' => $resp->msg . ' ,sub_msg :' . $resp->sub_msg . ' subcode:' . $resp->sub_code);
        }
    }
}
